home *** CD-ROM | disk | FTP | other *** search
/ CD Actual 1 / PC Actual CD 01.iso / f1 / cimb.arj / MAC.C < prev    next >
Encoding:
C/C++ Source or Header  |  1994-08-20  |  10.2 KB  |  495 lines

  1. /*==============================================================================
  2.  
  3. FICHERO: MAC.C
  4.  
  5. AUTOR: ANTONIO LADESA JURADO
  6.  
  7. FECHA: 24/6/94
  8.  
  9. DESCRIPCION:
  10.  
  11.     Fichero que contiene las estructuras, constantes, variables y funciones
  12.     internas y externas para el procesamiento de ficheros MAC.
  13.  
  14. ==============================================================================*/
  15.  
  16.  
  17. /*---- MODULOS USADOS --------------------------------------------------------*/
  18.  
  19. #include <stdio.h>
  20. #include <alloc.h>
  21. #include <string.h>
  22.  
  23. #include "global.h"
  24. #include "memoria.h"
  25. #include "mac.h"
  26. #include "error.h"
  27.  
  28.  
  29. /*----ESTRUCTURAS, CONSTANTES Y VARIABLES LOCALES AL MODULO ------------------*/
  30.  
  31.  
  32.     /* cabecera estandar de un fichero MAC */
  33. typedef struct
  34. {
  35. char byte_cero;
  36. char longitud;
  37. char nombre[63];
  38. char tipo[4];
  39. char creador[4];
  40. char relleno1[10];
  41. long tam_datos;
  42. long tam_codigo;
  43. long creacion;
  44. long modificacion;
  45. char relleno2[33];
  46. char patrones[304];
  47. char relleno3[204];
  48. }CABmac;
  49.  
  50.     /* cabecera del fichero MAC */
  51. static CABmac cabecera;
  52.  
  53.  
  54. /*---- DEFINICION DE LAS FUNCIONES INTERNAS ----------------------------------*/
  55.  
  56.  
  57. int MACleerImagen(IMAGEN *c,FILE *f);
  58. IMAGEN *MACleerCabecera(IMAGEN *c,FILE *f,char *nombre);
  59. int MACleerLinea(char *p,FILE *f);
  60.  
  61. void MACcrearCabecera(IMAGEN *c);
  62. int  MACescribirLinea(char *p,FILE *f);
  63. void MACescribirImagen(IMAGEN *c,FILE *f);
  64.  
  65.  
  66. /*---- CODIFICACION DE LAS FUNCIONES OFRECIDAS -------------------------------*/
  67.  
  68.  
  69. /*---- FUNCION: extern IMAGEN *MACcargar(char *nombre,IMAGEN *c) ---------------------
  70.  
  71.     Descripción:
  72.  
  73.         Esta función carga en memoria un fichero de tipo MAC.
  74.  
  75.     Parámetros:
  76.  
  77.         char *nombre : nombre del fichero a cargar
  78.         IMAGEN *c : puntero a estructura que alberga la imagen
  79.  
  80.     Retorno:
  81.  
  82.         - Puntero a la estructura de la imagen
  83.         - NULL si hubo error
  84.  
  85. ---- CODIGO: -----------------------------------------------------------------*/
  86.  
  87. extern IMAGEN *MACcargar(char *nombre,IMAGEN *c)
  88. {
  89.     /* puntero al fichero de entrada */
  90. FILE *f;
  91.  
  92.     /* abrir fichero */
  93. if((f=fopen(nombre,"rb")) != NULL)
  94.     {
  95.         /* leer cabecera MAC */
  96.     if((c = MACleerCabecera(c,f,nombre))!=NULL)
  97.         {
  98.             /* cargar imagen MAC */
  99.         if(MACleerImagen(c,f)!=72)
  100.             {
  101.             /* si no es MAC */
  102.             c = MEMliberar(c);
  103.             ERRORponer(ERRlectura);
  104.             }
  105.         }
  106.     }
  107. else
  108.     {
  109.     ERRORponer(ERRapertura);
  110.     return(NULL);
  111.     }
  112.     /* cerrar fichero y devolver cabecera */
  113. fclose(f);
  114. return(c);
  115. }
  116.  
  117. /*---- FIN FUNCION -----------------------------------------------------------------*/
  118.  
  119.  
  120. /*---- FUNCION: extern int MACsalvar(char *fichero,IMAGEN *c) ---------------------
  121.  
  122.     Descripción:
  123.  
  124.         Esta función salva en disco una imagen con formato MAC.
  125.  
  126.     Parámetros:
  127.  
  128.         char *nombre : nombre del fichero a cargar
  129.         IMAGEN *c : puntero a estructura que alberga la imagen
  130.  
  131.     Retorno:
  132.  
  133.         - 0 si hay error
  134.         - 1 en caso contrario
  135.  
  136. ---- CODIGO: -----------------------------------------------------------------*/
  137.  
  138. extern int MACsalvar(char *fichero,IMAGEN *c)
  139. {
  140.     /* puntero al fichero de salida */
  141. FILE *f;
  142.  
  143.     /* si no es monocromo, no se puede salvar como MAC */
  144. if(c->modo != VIDEOmono)
  145.     {
  146.     ERRORponer(ERRformato);
  147.     return(0);
  148.     }
  149.     /* abrir el fichero */
  150. if((f = fopen(fichero, "wb")) == NULL)
  151.     {
  152.     ERRORponer(ERRapertura);
  153.     return(0);
  154.     }
  155.  
  156.     /* crear la cabecera MAC */
  157. MACcrearCabecera(c);
  158.  
  159.     /* escribir la cabecera MAC */
  160. if(fwrite((char *)&cabecera,1,sizeof(CABmac),f) != sizeof(CABmac))
  161.     {
  162.     ERRORponer(ERRescritura);
  163.     return(0);
  164.     }
  165.     /* escribir la imagen MAC */
  166. MACescribirImagen(c,f);
  167.  
  168. fclose(f);
  169. return(1);
  170. }
  171.  
  172. /*---- FIN FUNCION --------------------------------------------------------------*/
  173.  
  174.  
  175. /*---- CODIFICACION DE LAS FUNCIONES INTERNAS --------------------------------*/
  176.  
  177.  
  178. /*---- FUNCION: IMAGEN *MACleerCabecera(IMAGEN *c,FILE *f,char *nombre) -------------
  179.  
  180.     Descripción:
  181.  
  182.         Esta función reserva memoria para la imagen y lee la cabecera del fichero
  183.         MAC.
  184.  
  185.     Parámetros:
  186.  
  187.         IMAGEN *c : puntero a estructura que alberga la imagen
  188.         FILE *f : puntero al fichero
  189.         char *nombre : nombre del fichero a cargar
  190.  
  191.     Retorno:
  192.  
  193.         - Puntero a la estructura de la imagen
  194.         - NULL si hubo error
  195.  
  196. ---- CODIGO: -----------------------------------------------------------------*/
  197.  
  198. IMAGEN *MACleerCabecera(IMAGEN *c,FILE *f,char *nombre)
  199. {
  200.     /* leer cabecera MAC */
  201. if(fread((char *)&cabecera,1,sizeof(CABmac),f)==sizeof(CABmac))
  202.     {
  203.         /* si es cabecera de 512 bytes... */
  204.     if(memcmp(cabecera.tipo,"PNTG",4))
  205.         /* ...retroceder 128 bytes */
  206.         fseek(f,-(128),SEEK_CUR);
  207.  
  208.         /* reservar memoria para la cabecera de trabajo */
  209.     if((c=MEMreservarCAB(c))==NULL)
  210.         {
  211.         ERRORponer(ERRnoMemoria);
  212.         return(NULL);
  213.         }
  214.  
  215.         /* cargar cabecera de trabajo */
  216.     strcpy(c->nombre,nombre);
  217.     c->ancho = 576;
  218.     c->alto = 720;
  219.     c->bytes = 72;
  220.     c->formato = MACPAINT;
  221.     c->modo = VIDEOmono;
  222.     c->colores = 2;
  223.     c->haypaleta = FALSO;
  224.  
  225.         /* reservar memoria para la imagen */
  226.     if(!MEMreservar(c))
  227.         /* si no hay memoria, liberar cabecera */
  228.         {
  229.         c = MEMliberar(c);
  230.         ERRORponer(ERRnoMemoria);
  231.         return(c);
  232.         }
  233.     }
  234. else
  235.     {
  236.     ERRORponer(ERRlectura);
  237.     return(NULL);
  238.     }
  239. return(c);
  240. }
  241.  
  242. /*---- FIN FUNCION ----------------------------------------------------------------*/
  243.  
  244.  
  245. /*---- FUNCION: int MACleerImagen(IMAGEN *c,FILE *f) -----------------------------
  246.  
  247.     Descripción:
  248.  
  249.         Esta función carga en memoria una imagen de tipo MAC.
  250.  
  251.     Parámetros:
  252.  
  253.         IMAGEN *c : puntero a estructura que alberga la imagen
  254.         FILE *f: puntero al fichero
  255.  
  256.     Retorno:
  257.  
  258.         - 72 si se ha leido correctamente
  259.         - cualquier otro número si hubo error
  260.  
  261. ---- CODIGO: -----------------------------------------------------------------*/
  262.  
  263. int MACleerImagen(IMAGEN *c,FILE *f)
  264. {
  265.     /* contador de lineas */
  266. int i;
  267.     /* bytes por linea */
  268. int n;
  269.     /* buffer */
  270. char p[256];
  271.  
  272.     /* hasta las 720 lineas... */
  273. for(i=0;i<720;++i)
  274.     {
  275.         /* leer linea */
  276.     if((n=MACleerLinea(p,f))!= 72)
  277.         {
  278.             /* si no tiene 72 bytes */
  279.         break;
  280.         }
  281.         /* llevar linea a memoria */
  282.     MEMescribir(p,i,c);
  283.     }
  284. return(n);
  285. }
  286.  
  287. /*---- FIN FUNCION -------------------------------------------------------------*/
  288.  
  289.  
  290. /*---- FUNCION: int MACleerLinea(char *p,FILE *f) -----------------------------
  291.  
  292.     Descripción:
  293.  
  294.         Esta función lee una línea de un fichero de tipo MAC.
  295.  
  296.     Parámetros:
  297.  
  298.         char *p : puntero a buffer dode se almacena la línea
  299.         FILE *f: puntero al fichero
  300.  
  301.     Retorno:
  302.  
  303.         - 72 si se ha leido correctamente
  304.         - 0  si hubo error
  305.  
  306. ---- CODIGO: -----------------------------------------------------------------*/
  307.  
  308. int MACleerLinea(char *p,FILE *f)
  309. {
  310.     /* caracter leido */
  311. int c;
  312.     /* contador de repeticion */
  313. int i;
  314.     /* contador de bytes por linea */
  315. int n=0;
  316.  
  317. do
  318.     {
  319.         /* lee caracter del fichero */
  320.     c=fgetc(f) & 0xff;
  321.  
  322.         /* si el bit 7 es 1... */
  323.     if(c & 0x80)
  324.         {
  325.             /* calcular complemento a 2 y usarlo como contador */
  326.         i = ((~c) & 0xff)+2;
  327.             /* leer siguiente byte */
  328.         c =fgetc(f);
  329.             /* cargarlo 'i' veces */
  330.         while(i--)
  331.             p[n++] = ~c;
  332.         }
  333.     else
  334.             /* si el bit 7 es 0... */
  335.         {
  336.             /* tomar contador */
  337.         i =(c & 0xff)+1;
  338.             /* leer 'i' bytes */
  339.         while(i--)
  340.             p[n++] = 0xff & ~(fgetc(f));
  341.         }
  342.     }
  343.     /* ...hasta 72 bytes maximo */
  344. while(n < 72);
  345.  
  346.     /* si hay fin de fichero imprevisto */
  347. if(c == EOF)
  348.     n=0;
  349. return(n);
  350. }
  351.  
  352. /*---- FIN FUNCION ----------------------------------------------------------*/
  353.  
  354.  
  355. /*---- FUNCION: int MACcrearCabecera(IMAGEN *c) -----------------------------------
  356.  
  357.     Descripción:
  358.  
  359.         Esta función crea una cabecera de tipo MAC.
  360.  
  361.     Parámetros:
  362.  
  363.         IMAGEN *c : puntero a estructura que alberga la imagen
  364.  
  365. ---- CODIGO: -----------------------------------------------------------------*/
  366.  
  367. void MACcrearCabecera(IMAGEN *c)
  368. {
  369.     /* rellena los datos de la cabecera */
  370. cabecera.byte_cero=0;
  371. cabecera.longitud=strlen(c->nombre);
  372. strcpy(cabecera.nombre,c->nombre);
  373. strcpy(cabecera.tipo,"PNTG");
  374. strcpy(cabecera.creador,"MPNT");
  375. memchr(cabecera.relleno1,' ',10);
  376. cabecera.tam_datos = 0;
  377. cabecera.tam_codigo = 0;
  378. cabecera.creacion = 0;
  379. cabecera.modificacion = 0;
  380. memchr(cabecera.relleno2,' ',33);
  381. memchr(cabecera.patrones,' ',304);
  382. memchr(cabecera.relleno3,' ',204);
  383. }
  384.  
  385. /*-- FIN FUNCION ----------------------------------------------------------------*/
  386.  
  387.  
  388. /*---- FUNCION: void MACescribirImagen(IMAGEN *c,FILE *f) -----------------------------
  389.  
  390.     Descripción:
  391.  
  392.         Esta función graba la imagen en un fichero de tipo MAC.
  393.  
  394.     Parámetros:
  395.  
  396.         IMAGEN *c : puntero a estructura que alberga la imagen
  397.         FILE *f: puntero al fichero
  398.  
  399. ---- CODIGO: -----------------------------------------------------------------*/
  400.  
  401. void MACescribirImagen(IMAGEN *c,FILE *f)
  402. {
  403.     /* contador de lineas */
  404. int i;
  405.     /* bytes por linea */
  406. int bytes;
  407.     /* buffers temporales para la linea */
  408. char p[1024];
  409. char q[72];
  410.  
  411.     /* obtener el numero de bytes */
  412. bytes = (c->bytes > 72) ? 72 : c->bytes;
  413.  
  414.     /* salvar imagen */
  415. for(i = 0; i < c->alto;++i)
  416.     {
  417.     MEMleer(p,i,c);
  418.     memset(q,0,72);
  419.     memcpy(q,p,bytes);
  420.     MACescribirLinea(p,f);
  421.     }
  422. for(;i<720;++i)
  423.     {
  424.     memset(p,0,72);
  425.     MACescribirLinea(p,f);
  426.     }
  427. }
  428.  
  429. /*-- FIN FUNCION ----------------------------------------------------------------*/
  430.  
  431.  
  432. /*---- FUNCION: void MACescribirLinea(char *p,FILE *f) -------------------------
  433.  
  434.     Descripción:
  435.  
  436.         Esta función comprime una línea en formato MAC y la graba en un fichero.
  437.  
  438.     Parámetros:
  439.  
  440.         char *p : puntero a buffer que alberga la línea
  441.         FILE *f : puntero al fichero
  442.  
  443. ---- CODIGO: -----------------------------------------------------------------*/
  444.  
  445.  
  446. int MACescribirLinea(char *p,FILE *f)
  447. {
  448.     /* buffer temporal */
  449. char b[72];
  450. int bdex=0,
  451. i=0,
  452. j=0,
  453. t=0;
  454.  
  455. do
  456.     {
  457.     i=0;
  458.     while((p[t+i]==p[t+i+1]) && ((t+i) < 71))
  459.         ++i;
  460.         /* si se repiten los datos... */
  461.     if(i>0)
  462.         {
  463.             /* paquete de bytes distintos */
  464.         if(bdex)
  465.             {
  466.             fputc(((bdex-1) & 0x7F),f);
  467.             j+=1;
  468.             fwrite(b,1,bdex,f);
  469.             j+=bdex;
  470.             bdex=0;
  471.             }
  472.         /* paquete de bytes iguales */
  473.         fputc((~i+1),f);
  474.         fputc(~p[t+i],f);
  475.         j+=2;
  476.         t+=(i+1);
  477.         }
  478.     else
  479.         b[bdex++]=~p[t++];
  480.     }while(t<72);
  481.  
  482.     /* si quedan bytes pendientes... */
  483. if(bdex)
  484.     {
  485.     fputc(((bdex-1) & 0x7F),f);
  486.     j+=1;
  487.     fwrite(b,1,bdex,f);
  488.     j+=bdex;
  489.     bdex=0;
  490.     }
  491. return(j);
  492. }
  493.  
  494. /*---- FIN FUNCION -----------------------------------------------------------*/
  495.